package com.example.shrio;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.admin.entity.SysPermission;
import com.example.admin.entity.SysRole;
import com.example.admin.entity.SysUser;
import com.example.admin.service.ISysRoleService;
import com.example.admin.service.ISysUserService;
import com.example.shrio.conf.CustomizedToken;
import com.example.shrio.error.LoginNullUserException;
import com.example.shrio.error.LoginPassWordException;
import com.example.util.encryption.EncryptionUtil;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;

import javax.annotation.Resource;
import java.util.List;

/**
 * 自定义认证、权限（系統用戶）
 *
 * @author wangkai
 * @date: 2019年5月31日 下午1:15:15
 */
public class AdminUserShiroRealm extends AuthorizingRealm {

    @Autowired
    private ISysUserService userService;
    @Autowired
    private ISysRoleService service;

    /*
     * (non-Javadoc) 认证
     *
     * @see
     * org.apache.shiro.realm.AuthenticatingRealm#doGetAuthenticationInfo(org.
     * apache.shiro.authc.AuthenticationToken)
     */
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        // 获取用户的输入的账号.
        CustomizedToken customizedToken = (CustomizedToken) token;
        String account = (String) customizedToken.getPrincipal();
        QueryWrapper<SysUser> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("account", account);
        SysUser userInfo = userService.getOne(queryWrapper);
        if (userInfo == null) {
            throw new LoginNullUserException("当前账号未注册");
        }
        String password = new String((char[]) token.getCredentials());
        String newPassword = EncryptionUtil.encryptionMd5(password, userInfo.getSalt(), 2);
        if (!newPassword.equals(userInfo.getPassword())) {
            throw new LoginPassWordException("当前输入密码不正确");
        }
        if (userInfo.getStart().intValue() == 1) { // 账户冻结
            throw new LockedAccountException("账户冻结");
        }
        if (!userInfo.getAccount().equals("admin")) {
            List<SysRole> users = service.getRoleList(userInfo.getId());
            userInfo.setRoleList(users);
        }
        SimpleAuthenticationInfo authenticationInfo = new SimpleAuthenticationInfo(userInfo, // 用户
                password, // 密码
                getName() // realm name
        );
        return authenticationInfo;
    }

    /*
     * (non-Javadoc) 分配权限
     *
     * @see
     * org.apache.shiro.realm.AuthorizingRealm#doGetAuthorizationInfo(org.apache
     * .shiro.subject.PrincipalCollection)
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
        SysUser userInfo = (SysUser) principals.getPrimaryPrincipal();
        if (userInfo != null && userInfo.getRoleList() != null) {
            for (SysRole role : userInfo.getRoleList()) {
                authorizationInfo.addRole(role.getCode());
                for (SysPermission p : role.getPermissions()) {
                    authorizationInfo.addStringPermission(p.getPermission());
                }
            }
        }
        return authorizationInfo;
    }

}
